<?php
// +----------------------------------------------------------------------
// | ZanPianCMS [ WE CAN DO IT JUST THINK IT ]
// +----------------------------------------------------------------------
// | Copyright (c) 2013 http://www.zanpian.com All rights reserved.
// +----------------------------------------------------------------------
// | BBS:  <http://www.feifeicms.cc>
// +----------------------------------------------------------------------
namespace app\common\model;
use think\Model;
class WeixinPay extends Model{
    public function submit($user_id,$score_ext){
		config('pathinfo_depr','/');
        $total_fee = sprintf("%.2f",$score_ext);
        $data = array();
        $data['appid'] =  trim($GLOBALS['config']['user']['pay']['weixin_app_id']);//公众号
        $data['mch_id'] =  trim($GLOBALS['config']['user']['pay']['weixin_mch_id']);//商户号
        $data['nonce_str'] =  rand_string(32);//随机字符串
        $data['body'] =  '积分充值（UID：'.$user_id.'）';//商品描述
        $data['fee_type'] =  'CNY';//标价币种
        $data['out_trade_no'] = date("YmdHis").mt_rand(10000, 99999);//商户订单号
        $data['total_fee'] = $total_fee*100;//金额，单位分
        $data['spbill_create_ip'] =  request()->ip();//终端IP
        $data['notify_url'] =  url('home/notify/weixinpay',[],false,true);
        $data['trade_type'] =  'NATIVE';//交易类型 JSAPI，NATIVE，APP
        $data['product_id'] = '1';//商品ID
        //$data['openid'] =  '';//用户标识 trade_type=JSAPI时（即公众号支付），此参数必传
        $data['sign'] =  $this->makeSign($data);
        //获取付款二维码
        $data_xml = $this->array2xml($data);
        $res = zanpian_curl_post('https://api.mch.weixin.qq.com/pay/unifiedorder', $data_xml);
        $res = $this->xml2array($res);
        if($res['return_code']=='SUCCESS' && $res['result_code']=='SUCCESS'){
            //返回付款信息
            $res = [
			    'order_uid'=>$user_id,
			    'order_sign'=>$data['out_trade_no'],
				'order_money'=>$total_fee,
				'order_info' =>$data['body'],
				'order_type'=>'weixin',
                'order_code'=>$res['code_url']
            ];
		    //写入订单
			if(model('Orders')->data($res)->save()!== false){
				$res['order_id']=model('Orders')->order_id;
			}
            			
            //echo '<img src=http://paysdk.weixin.qq.com/example/qrcode.php?data='.urlencode($res['code_url']).'/>';
            return $res;
        }
        //echo '获取微信二维码失败,'.$res['return_msg'];
        return false;
    }
    public function notify(){
        $xml = file_get_contents('php://input');
        //将服务器返回的XML数据转化为数组
        $data = $this->xml2array($xml);     
        // 保存微信服务器返回的签名sign
        $data_sign = $data['sign'];
        // sign不参与签名算法
        unset($data['sign']);
        // 生成签名
        $sign = $this->makeSign($data);
		if($GLOBALS['config']['user']['pay']['pay_notify']==1){
            file_put_contents(RUNTIME_PATH.'notify.txt', "收到来自微信的异步通知\r\n", FILE_APPEND);
            file_put_contents(RUNTIME_PATH.'notify.txt', "订单单号：{$data['out_trade_no']}\r\n", FILE_APPEND);
            file_put_contents(RUNTIME_PATH.'notify.txt', "订单金额：{$data['total_fee']}\r\n\r\n", FILE_APPEND);
            file_put_contents(RUNTIME_PATH.'notify.txt', '支付状态：' . $data['return_code'] . "\r\n\r\n", FILE_APPEND);			
        }		
        // 判断签名是否正确  判断支付状态
        if (($sign===$data_sign) && ($data['return_code']=='SUCCESS') && ($data['result_code']=='SUCCESS') ) {
                if( model('Orders')->update_order($data['out_trade_no'],$data['total_fee']*0.01)!== false){
                     echo '<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>';
                }
                else{
                    echo '<xml><return_code><![CDATA[FAIL]]></return_code><return_msg><![CDATA[签名失败]]></return_msg></xml>';
                }
        }
        else{
            echo '<xml><return_code><![CDATA[FAIL]]></return_code><return_msg><![CDATA[签名失败]]></return_msg></xml>';
        }
    }

    public function makeSign($data){
        //获取微信支付秘钥
        $key = trim($GLOBALS['config']['user']['pay']['weixin_mch_key']);
        // 去空
        $data=array_filter($data);
        //签名步骤一：按字典序排序参数
        ksort($data);
        $string_a=http_build_query($data);
        $string_a=urldecode($string_a);
        //签名步骤二：在string后加入KEY
        $string_sign_temp=$string_a."&key=".$key;
        //签名步骤三：MD5加密
        $sign = md5($string_sign_temp);
        // 签名步骤四：所有字符转为大写
        $result=strtoupper($sign);
        return $result;
    }
public function array2xml($arr,$level=1)
{
    $s = $level == 1 ? "<xml>" : '';
    foreach($arr as $tagname => $value) {
        if (is_numeric($tagname)) {
            $tagname = $value['TagName'];
            unset($value['TagName']);
        }
        if(!is_array($value)) {
            $s .= "<{$tagname}>".(!is_numeric($value) ? '<![CDATA[' : '').$value.(!is_numeric($value) ? ']]>' : '')."</{$tagname}>";
        } else {
            $s .= "<{$tagname}>" . $this->array2xml($value, $level + 1)."</{$tagname}>";
        }
    }
    $s = preg_replace("/([\x01-\x08\x0b-\x0c\x0e-\x1f])+/", ' ', $s);
    return $level == 1 ? $s."</xml>" : $s;
}


public function xml2array($xml)
{
    libxml_disable_entity_loader(true);
    $result= json_decode(json_encode(simplexml_load_string($xml, 'SimpleXMLElement', LIBXML_NOCDATA)), true);
    return $result;
}	
}